import os
import sys
import FileNeedToGenerate

def SettingKeyValue(key, type, value):
	str_code = ["", "", "", "", "", ""]

	str_code[3] += "\tif (strcmp(key, \"" + key + "\") == 0)\n"
	str_code[3] += "\t{\n"

	if type == "int8_t":
		str_code[3] += "\t\tg_Settings->" + key + " = strtol(value, NULL, 0);\n"

	if type == "uint8_t":
		str_code[3] += "\t\tg_Settings->" + key + " = strtoul(value, NULL, 0);\n"

	if type == "int16_t":
		str_code[3] += "\t\tg_Settings->" + key + " = strtol(value, NULL, 0);\n"

	if type == "uint16_t":
		str_code[3] += "\t\tg_Settings->" + key + " = strtoul(value, NULL, 0);\n"

	if type == "int32_t":
		str_code[3] += "\t\tg_Settings->" + key + " = strtol(value, NULL, 0);\n"

	if type == "uint32_t":
		str_code[3] += "\t\tg_Settings->" + key + " = strtoul(value, NULL, 0);\n"

	if type == "int64_t":
		str_code[3] += "\t\tg_Settings->" + key + " = strtoll(value, NULL, 0);\n"

	if type == "uint64_t":
		str_code[3] += "\t\tg_Settings->" + key + " = strtoull(value, NULL, 0);\n"

	if type == "float":
		str_code[3] += "\t\tg_Settings->" + key + " = strtof(value, NULL);\n"

	if type == "double":
		str_code[3] += "\t\tg_Settings->" + key + " = strtod(value, NULL);\n"

	if type == "string":
		str_code[3] += "\t\tstrncpy(g_Settings->" + key + ", value, 200);\n"

	str_code[3] += "\t\treturn 0;\n"
	str_code[3] += "\t}\n"

	##########################################################################################

	str_format = "%d"

	if type == "int8_t":
		str_format = "%\" PRId8 \""

	if type == "uint8_t":
		str_format = "%\" PRIu8 \""

	if type == "int16_t":
		str_format = "%\" PRId16 \""

	if type == "uint16_t":
		str_format = "%\" PRIu16 \""

	if type == "int32_t":
		str_format = "%\" PRId32 \""

	if type == "uint32_t":
		str_format = "%\" PRIu32 \""

	if type == "int64_t":
		str_format = "%\" PRId64 \""

	if type == "uint64_t":
		str_format = "%\" PRIu64 \""

	if type == "float":
		str_format = "%.7f"

	if type == "double":
		str_format = "%.10lf"

	if type == "string":
		str_format = "%s"

	##########################################################################################
	
	str_code[2] += "\tif (strcmp(key, \"" + key + "\") == 0)\n"
	str_code[2] += "\t{\n"
	str_code[2] += "\t\tsnprintf(value, 200, \"" + str_format + "\", g_Settings->" + key + ");\n"
	str_code[2] += "\t\treturn 0;\n"
	str_code[2] += "\t}\n"

	##########################################################################################

	str_code[4] += "\tret = snprintf(line, line_size, \"" + key + "=" + str_format + "\\n\", g_Settings->" + key + ");\n"
	str_code[4] += "\twrite(fd, line, ret);\n"

	str_code[5] += "\tif (callback == NULL)\n"
	str_code[5] += "\t{\n"
	str_code[5] += "\t\tLOGI(\"" + key + " = " + str_format + "\\n\", g_Settings->" + key + ");\n"
	str_code[5] += "\t}\n"
	str_code[5] += "\telse\n"
	str_code[5] += "\t{\n"
	str_code[5] += "\t\tchar value[200] = {0};\n"
	str_code[5] += "\t\tsnprintf(value, 200, \"" + str_format + "\", g_Settings->" + key + ");\n"
	str_code[5] += "\t\tcallback(\"" + key + "\", value, arg);\n"
	str_code[5] += "\t}\n\n"

	##########################################################################################

	if type == "string":
		str_code[0] += "\tchar " + key + "[200];\n"
	else:
		str_code[0] += "\t" + type + " " + key + ";\n"

	##########################################################################################

	if type == "string":
		str_code[1] += "\tstrncpy(g_Settings->" + key + ", \"" + value + "\", 200);\n"
	else:
		str_code[1] += "\tg_Settings->" + key + " = " + value + ";\n"

	return str_code

def FindSettingsKeyValue(line):
	str_code = ["", "", "", "", "", ""]

	if "@SettingKeyValue" in line:
		line = line.replace('\n', '')
		line = line.replace('\r', '')
		line = line.replace('\t', ' ')
		while True:
			if '  ' in line:
				line = line.replace('  ', ' ')
			else:
				break
		strs = line.split(" ")
		i = 0
		ind = 0
		for str in strs:
			if "@SettingKeyValue" in str:
				ind = i
			i += 1
		text = SettingKeyValue(strs[ind+1], strs[ind+2], strs[ind+3])
		for i in range (6) :
			str_code[i] += text[i]
	
	return str_code

def ReadFile(filename):
	str_code = ["", "", "", "", "", ""]

	file = open(filename, "r", encoding="utf-8")
	line = " "
	while line:
		line = file.readline()
		if len(line) > 0:
			text = FindSettingsKeyValue (line)
			for i in range (6) :
				str_code[i] += text[i]
	file.close()
	return str_code

def WriteFile(tar_struct_path, filename, str_code):
	file = open(tar_struct_path, "w", encoding="utf-8")
	file.write(str_code[0])
	file.close()

	file = open(filename, "w", encoding="utf-8")
	file.write(str_code[3])
	file.write(str_code[4])
	file.write(str_code[1])
	file.write(str_code[2])
	file.write(str_code[5])
	file.close()

def MakeSettingKeyValue(src_path, tar_path, tar_struct_path):
	str_code = ["", "", "", "", "", ""]

	str_code[0] =  "#ifndef __PY_SETTING_STRUCT_H_\n"
	str_code[0] += "#define __PY_SETTING_STRUCT_H_\n"
	str_code[0] += "\n#include <stdint.h>\n\ntypedef struct\n"
	str_code[0] += "{\n"

	str_code[1] = "\nvoid py_settings_reset(void)\n"
	str_code[1] += "{\n"

	str_code[2] = "\nint py_settings_key_value_get(char *key, char *value)\n"
	str_code[2] += "{\n"

	str_code[3] = "#include <stdio.h>\n"
	str_code[3] += "#include <stdlib.h>\n"
	str_code[3] += "#include <fcntl.h>\n"
	str_code[3] += "#include <inttypes.h>\n"
	str_code[3] += "#include <py_settings_struct.hpp>\n"
	str_code[3] += "#include <settings.hpp>\n"
	str_code[3] += "\nint py_settings_key_value_set(char *key, char *value)\n{\n"

	str_code[4] = "\nvoid py_settings_key_value_save(int fd, char* line, int line_size)\n{\n\tint ret = 0;\n"

	str_code[5] = "\nvoid py_settings_key_value_display(void(*callback)(const char*, char*, void*), void* arg)\n{\n"

	# for dirpath,dirname,filename in os.walk(src_path):
	# 	for name in filename:
	# 		if name.endswith(".ini"):
	# 			filepath = os.path.join(dirpath,name)
	# 			text = ReadFile(filepath)
	# 			for i in range (6) :
	# 				str_code[i] += text[i]
	print(src_path)
	text = ReadFile(src_path)
	for i in range (6) :
		str_code[i] += text[i]

	str_code[0] += "\n} settings_s;\n"
	str_code[0] += "\n#endif\n"

	str_code[1] += "\n}\n"
	str_code[2] += "\n\treturn -1;\n"
	str_code[2] += "\n}\n"
	str_code[3] += "\n\treturn -1;\n"
	str_code[3] += "\n}\n"
	str_code[4] += "}\n"
	str_code[5] += "}\n"
	WriteFile(tar_path, tar_struct_path, str_code)

def main(foldername):
	#如果目录不存在则创建目录
	ret = os.path.exists("./build/" + foldername + "/py_cpp/")
	if not ret:
		os.mkdir("./build/" + foldername + "/py_cpp/")

	origin_ini_file = "./src/system/settings/settings.ini"

	hash_file = "./build/" + foldername + "/py_cpp/hash_setting.txt"
	hash_list = FileNeedToGenerate.GetLastFileHashCode(hash_file)
	current_hash = FileNeedToGenerate.GetFileHashCode(origin_ini_file)

	isNeed = False
	if origin_ini_file in hash_list:
		if current_hash == hash_list[origin_ini_file]:
			isNeed = False
		else:
			isNeed = True
	else:
		isNeed = True
	
	hash_list[origin_ini_file] = current_hash
	FileNeedToGenerate.FileSaveHashList(hash_file, hash_list)
	
	if isNeed:
		MakeSettingKeyValue(origin_ini_file, "./build/" + foldername + "/py_cpp/py_settings_struct.hpp", "./build/" + foldername + "/py_cpp/py_settings_key_value.cpp")
